#include "stdafx.h"
#include "stdio.h"
#include "stdlib.h"
#include "lscoroutin.h"

static tcb_t mstatic_tcb_pool[MAX_TASK_NUM];
static tcb_t* mroot_tcb = NULL;
tcb_t* mpcurtcb;
int msp;
int mstktop;
int margcaddr;
static int mtasknum;

 
static void os_taskidle(void *name);

void os_init(int heaptopaddr){

	mstktop = heaptopaddr;
    mtasknum = 0;
	LOG_I("the stack=%d in [%s]\n",mstktop,"main.c");
	//setup root task
	mroot_tcb = mpcurtcb = &mstatic_tcb_pool[mtasknum++];//new tcb_t;
	
	mstktop -= 8;// for idle input param 
	mpcurtcb->stktop = mstktop;
    mstktop -=IDLE_TASK_STACK_SIZE;

	mpcurtcb->benvinit = 0;
	mpcurtcb->taskentry = os_taskidle;
	mpcurtcb->next = mroot_tcb;
	//mpcurtcb->tasksta = STA_INIT;
}

int os_createtask(char* taskname , void (*task)(void* taskname), void*arg, int stacksize ){
	tcb_t *ptcb;// = new tcb_t;

    if(mtasknum >= MAX_TASK_NUM){
        return -1;
    }

    ptcb = &mstatic_tcb_pool[mtasknum++];

	ptcb->stktop = mstktop;
	mstktop -= stacksize;

	ptcb->taskentry = task;
	ptcb->arg = arg;
	ptcb->benvinit = 0;

	mpcurtcb->next = ptcb;
	ptcb->next = mroot_tcb;
	
	mpcurtcb = ptcb;
	return 0;
	
}


// should never return...
int os_runtasks(void){

	mpcurtcb->taskentry(mpcurtcb->arg);
	return 0;
}

//int mwaitflag_idle = 0; 

/*
函数调用过程的惯例：
1.函数局部变量采用堆栈的方式管理，由ebp 确定栈帧的基址；
2.函数的参数由右往左顺序入栈，(ebp + 8) 为最左的参数，
3.函数的返回值由 eax 寄存器存储；
4.函数的返回地址在(ebp + 4)
5.函数局部变量的地址偏移是 负数

call: 就是把下一指令地址装入 esp中,等价于 push pc;
ret :等价于 pop pc
   
*/
static void os_taskidle(void *param)
{
	//int starttick;
	//os_task_init(param);
	//starttick = 0;

	while(1){
		LOG_I("%s ,tick =%d\n","task idle",os_sys_tick());
        os_msleep(1000);
		// os_waifor(mwaitflag_idle == 1);

		// mwaitflag_idle = 0;

		// starttick += 1200;
	}
}
 